/*
 * 
 * LegendShop 多用户商城系统
 * 
 *  版权所有,并保留所有权利。
 * 
 */
package com.legendshop.util;

import java.io.BufferedReader;
import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.Serializable;
import java.security.MessageDigest;
import java.text.NumberFormat;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Calendar;
import java.util.Collection;
import java.util.GregorianCalendar;
import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.StringTokenizer;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import java.util.zip.CRC32;

import org.apache.commons.lang.StringUtils;
import org.apache.oro.text.regex.MalformedPatternException;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

/**
 * 
 * 应用工具类
 */
public class AppUtils {

	/** The log. */
	private final static Logger logger = LoggerFactory.getLogger(AppUtils.class);

	/**
	 * 获取日期的字符串格式为： MM/DD/YYYY
	 * 
	 */
	public static String getDisplayDate(Calendar pCalendar) {
		SimpleDateFormat format = new SimpleDateFormat("MM/dd/yyyy");
		if (pCalendar != null)
			return format.format(pCalendar.getTime());
		else
			return "";
	}

	/**
	 * 由字符串转变为Calendar
	 */
	public static Calendar str2Calendar(String str) {
		Calendar cal = null;
		if (isNotBlank(str)) {
			try {
				SimpleDateFormat sdf = new SimpleDateFormat("MM/dd/yyyy");
				java.util.Date d = sdf.parse(str);
				cal = Calendar.getInstance();
				cal.setTime(d);
			} catch (ParseException e) {
			}
		}
		return cal;
	}

	/**
	 * 获取当前时间. 格式为: MM/DD/YYYY
	 * 
	 * @return 当前时间
	 */
	public static String getCurrentDate() {
		return getDisplayDate(GregorianCalendar.getInstance());
	}


	/**
	 * 检查字符串是否为空.
	 * 
	 */
	public static boolean isBlank(final String str) {
		return (str == null) || (str.trim().length() <= 0);
	}

	/**
	 *检查字符串是否不为空.
	 * 
	 */
	public static boolean isNotBlank(final String str) {
		return !(isBlank(str));
	}

	/**
	 * 检查数组是否为空.
	 */
	public static boolean isBlank(final Object[] objs) {
		return (objs == null) || (objs.length <= 0);
	}

	/**
	 * 检查数组是否不为空.
	 */
	public static boolean isNotBlank(final Object[] objs) {
		return !(isBlank(objs));
	}

	/**
	 * 检查对象是否为空.
	 */
	public static boolean isBlank(final Object objs) {
		return (objs == null) || "".equals(objs);
	}

	/**
	 * 检查对象是否不为空.
	 */
	public static boolean isNotBlank(final Object objs) {
		return !(isBlank(objs));
	}

	/**
	 * 检查Collection是否为空.
	 */
	public static boolean isBlank(final Collection obj) {
		return (obj == null) || (obj.size() <= 0);
	}

	/**
	 * 检查Collection是否不为空.
	 */
	public static boolean isNotBlank(final Collection obj) {
		return !(isBlank(obj));
	}

	/**
	 * 检查Set是否为空.
	 */
	public static boolean isBlank(final Set obj) {
		return (obj == null) || (obj.size() <= 0);
	}

	/**
	 * 检查Set是否不为空.
	 */
	public static boolean isNotBlank(final Set obj) {
		return !(isBlank(obj));
	}

	/**
	 * 检查Serializable是否为空.
	 */
	public static boolean isBlank(final Serializable obj) {
		return obj == null;
	}

	/**
	 * 检查Serializable是否不为空.
	 */
	public static boolean isNotBlank(final Serializable obj) {
		return !(isBlank(obj));
	}

	/**
	 * 检查Map是否为空.
	 */
	public static boolean isBlank(final Map obj) {
		return (obj == null) || (obj.size() <= 0);
	}

	/**
	 * 检查Map是否不为空.
	 */
	public static boolean isNotBlank(final Map obj) {
		return !(isBlank(obj));
	}

	/**
	 * List转化为数组.
	 */
	public static String[] list2Strings(List<String> list) {
		String[] value = null;
		try {
			if (list == null)
				return null;
			value = new String[list.size()];
			for (int i = 0; i < list.size(); i++) {
				value[i] = (String) list.get(i);
			}
		} catch (Exception e) {
			logger.error("list is null: " + e);
		}
		return value;
	}

	/**
	 * List转化为字符串，用英文逗号隔开.
	 */
	public static String list2String(List<Object> list) {
		if (AppUtils.isBlank(list)) {
			return "";
		}
		StringBuffer sbuf = new StringBuffer();
		sbuf.append(list.get(0));
		for (int idx = 1; idx < list.size(); idx++) {
			sbuf.append(",");
			sbuf.append(list.get(idx));
		}
		return sbuf.toString();
	}

	/**
	 * 字符数组转化为List。
	 */
	public static List<String> Strings2List(String[] args) {
		List<String> list = new ArrayList<String>();
		try {
			if (args == null)
				return null;
			for (int i = 0; i < args.length; i++) {
				list.add(args[i]);
			}
		} catch (Exception e) {
			logger.error("list is null: " + e);
		}
		return list;
	}

	/**
	 * 将字符串按英文逗号隔开，返回字符数组
	 */
	public static String[] getStrings(String str) {
		List<String> values = getStringCollection(str);
		if (values.size() == 0) {
			return null;
		}
		return values.toArray(new String[values.size()]);
	}

	/**
	 * 将字符串按英文逗号隔开，返回字符List
	 */
	public static List<String> getStringCollection(String str) {
		List<String> values = new ArrayList<String>();
		if (str == null)
			return values;
		StringTokenizer tokenizer = new StringTokenizer(str, ",");
		values = new ArrayList<String>();
		while (tokenizer.hasMoreTokens()) {
			values.add(tokenizer.nextToken());
		}
		return values;
	}

	/**
	 * 实现：input框内可以输入多个字符，用空格或逗号分割查询条件，逗号和空格可以混用，最后把查询的条件一并列出 例如输入：中国，美国, 法国 德国，
	 * ，日本 ，可以将符合各国的条件一并查出，忽略不符合规则的输入
	 * 
	 * 需处理： 1.将多个空格格式化为一个空格 2.逗号分割既可用英文标点，又可以用中文标点 3.排除其他标点符号，如查询条件中有其他标点符号，则忽略掉
	 * 4.同时满足两个条件混查
	 * 
	 * @param keyword
	 *            关键字
	 * @return the string[] 查询结果
	 */
	public static String[] searchByKeyword(String keyword) {
		Pattern p = Pattern.compile("[' ']+").compile("[.。！？#@#￥$%&*()（）=《》<>‘、’；：\"\\?!:']");
		// 正则，过滤多余空格和其他中英文标点
		Matcher m = p.matcher(keyword);
		String list1 = m.replaceAll(" ").replaceAll("，", ",");
		// replaceAll 将中文逗号替换为英文逗号
		String list2 = StringUtils.replace(list1, " ", ",");
		// 将所有单个空格替换为英文逗号
		String[] list = StringUtils.split(list2, ",");
		// 英文逗号为界，分割为数组
		return list;
		// for (int j = 0; j < list.length; j++) {
		// System.out.println("list["+j+"]=" + list[j]);
		// //处理后的查询字符串
		// }
	}

	/**
	 * 格式化数字
	 * 设置数字的位数为8. 由实际情况的最大数字决定
	 * 是否按每三位隔开,如:1234567 将被格式化为 1,234,567。在这里选择 否
	 */
	public static String formatNumber(Long number) {
		if (number == null) {
			return null;
		}
		NumberFormat format = NumberFormat.getIntegerInstance();
		// 设置数字的位数 由实际情况的最大数字决定
		format.setMinimumIntegerDigits(8);
		// 是否按每三位隔开,如:1234567 将被格式化为 1,234,567。在这里选择 否
		format.setGroupingUsed(false);
		return format.format(number);
	}

	/**
	 * 获取CRC32值
	 * 
	 * @param value
	 *            the value
	 * @return the cR c32
	 */
	public static Long getCRC32(String value) {
		CRC32 crc32 = new CRC32();
		crc32.update(value.getBytes());
		return crc32.getValue();
	}



	/**
	 * 读入模版并将参数代进去.
	 * 
	 */
	public static String convertTemplate(String fileName, String pattern, Map values) throws MalformedPatternException {
		String record = null;
		StringBuffer sb = new StringBuffer();
		try {
			File inFile = new File(fileName);
			if (!inFile.exists()) {
				return sb.toString();
			}
			FileInputStream fileInputStream = new FileInputStream(inFile);
			BufferedReader inBufferedReader = new BufferedReader(new InputStreamReader(fileInputStream, "UTF-8"));

			record = new String();
			while ((record = inBufferedReader.readLine()) != null) {
				sb.append(StringUtil.convert(record, pattern, values) + "\n");
			}
			inBufferedReader.close();
			fileInputStream.close();
		} catch (IOException e) {
			System.out.println("got an IOException error!");
			e.printStackTrace();
		}
		return sb.toString();
	}

	/**
	 * 转换模板.
	 * 
	 */
	public static String convertTemplate(String fileName, Map values) throws MalformedPatternException {
		return convertTemplate(fileName, "\\#[a-zA-Z]+\\#", values);
	}

	/**
	 * 数组转化为字符串.
	 * 
	 * @param strs
	 *            the strs
	 * @return the string
	 */
	public static String arrayToString(String[] strs) {
		if (strs.length == 0) {
			return "";
		}
		StringBuffer sbuf = new StringBuffer();
		sbuf.append(strs[0]);
		for (int idx = 1; idx < strs.length; idx++) {
			sbuf.append(",");
			sbuf.append(strs[idx]);
		}
		return sbuf.toString();
	}

	/**
	 * 如果为空则返回默认值
	 */
	public static String getDefaultValue(String value, String defaultValue) {
		if (isNotBlank(value)) {
			return value;
		} else {
			return defaultValue;
		}
	}
	
	/**
	 * 加密算法
	 * algorithm： sha1, MD5
	 * @param password
	 * @param algorithm
	 * @return 加密的结果
	 */
	public static String encodePassword(String password, String algorithm) {
		byte[] unencodedPassword = password.getBytes();

		MessageDigest md = null;
		try {
			// first create an instance, given the provider
			md = MessageDigest.getInstance(algorithm);
		} catch (Exception e) {
			e.printStackTrace();
			return password;
		}
		md.reset();
		// call the update method one or more times
		// (useful when you don't know the size of your data, eg. stream)
		md.update(unencodedPassword);
		// now calculate the hash
		byte[] encodedPassword = md.digest();

		StringBuffer buf = new StringBuffer();

		for (int i = 0; i < encodedPassword.length; i++) {
			if ((encodedPassword[i] & 0xff) < 0x10) {
				buf.append("0");
			}

			buf.append(Long.toString(encodedPassword[i] & 0xff, 16));
		}

		return buf.toString();
	}
	
	/**
	 * 采用Md5进行加密
	 * @param password
	 * @return 加密的结果
	 */
	public static String md5(String password) {
		return encodePassword(password, "md5");
	}
	
	/**
	 * 采用sha1进行加密
	 * @param password
	 * @return 加密的结果
	 */
	public static String sha1(String password) {
		return encodePassword(password, "sha1");
	}
	
	/**
	 * 比较2个值是否一致
	 * @param a
	 * @param b
	 * @return
	 */
	public static boolean isTheSame(Object a, Object b) {
		if(a == null && b == null){
			return true;
		}
		if(a != null && a.equals(b)){
			return true;
		}
		return false;
	}
	
	/**
	 * 在微信中， 把颜文字去掉
	 * @param nickName
	 * @return
	 */
	public static String removeYanText(String nickName){
		if(AppUtils.isBlank(nickName)){
			return "";
		}
		byte[] b_text = nickName.getBytes();
		for (int i = 0; i < b_text.length; i++) {
			if((b_text[i] & 0xF8) == 0xF0){
				for (int j = 0; j < 4; j++) {
					b_text[i+j] = 0x00; //空字符
				}
				i+=3;
			}
		}
		return new String(b_text);
	}
	

}
